package com.koicarp.university.graduate.service.service.report.impl;

import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.koicarp.university.graduate.service.dao.ReportDao;
import com.koicarp.university.graduate.service.dao.ReportStatusDao;
import com.koicarp.university.graduate.service.dto.bigView.GraNumAddressDto;
import com.koicarp.university.graduate.service.dto.bigView.SalaryByAddressDto;
import com.koicarp.university.graduate.service.dto.bigView.SpecialityTopDto;
import com.koicarp.university.graduate.service.dto.dataCompare.SalaryByYearDto;
import com.koicarp.university.graduate.service.entity.report.Report;
import com.koicarp.university.graduate.service.entity.report.ReportStatus;
import com.koicarp.university.graduate.service.service.report.IReportService;
import com.koicarp.university.graduate.service.vo.dataCompare.EmployRateVo;
import com.koicarp.university.graduate.service.vo.wx.ReportVo;
import com.koicarp.university.graudate.common.constant.BaseConstant;
import com.koicarp.university.graudate.common.utils.UniversityResponse;
import com.koicarp.university.graudate.common.utils.UniversityUtil;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;

/**
 * 【报表管理：问卷年表】(Report)表服务实现类
 *
 * @author liutao
 * @since 2020-11-26 15:12:38
 */
@Slf4j
@Service("reportService")
@RequiredArgsConstructor
public class ReportServiceImpl extends ServiceImpl<ReportDao,Report> implements IReportService {

    private final ReportDao reportDao;

    private final ReportStatusDao reportStatusDao;
    @Override
    @Transactional
    public UniversityResponse saveReportInfo(ReportVo reportVo) {
        UniversityResponse response = new UniversityResponse();
        response.code(BaseConstant.RESPONSE_CODE_SUCCESS_200);
        response.message(BaseConstant.RESPONSE_MESSAGE_OPR_SUCCESS);

        Report report = new Report();
        BeanUtils.copyProperties(reportVo,report);
        reportDao.insert(report);
        ReportStatus reportStatus = new ReportStatus();
        reportStatus.setGraduateId(reportVo.getGraduateId());
        reportStatus.setReportId(report.getId());
        reportStatus.setWriteYear(new Date());
        reportStatus.setYear(UniversityUtil.nowYear());
        reportStatusDao.insert(reportStatus);
        /*
        * 先插入到report表返回reportid
        * 再插入report_status表
        *
        * */
        return response;
    }

    @Override
    public UniversityResponse getSpecialityTop(){
        UniversityResponse response = new UniversityResponse();
        response.code(BaseConstant.RESPONSE_CODE_SUCCESS_200);
        response.message(BaseConstant.RESPONSE_MESSAGE_OPR_SUCCESS);
        Date date = new Date();
        SimpleDateFormat format = new SimpleDateFormat("yyyy");
        String year ="%" + format.format(date)+ "%";
        List<SpecialityTopDto> list = reportDao.selectSpecialityTop(year);
        int i = 0;
        List<SpecialityTopDto> top = new ArrayList<>();
        HashMap<String,String> vis = new HashMap<>();
        for (SpecialityTopDto stdto: list){
            if(i>=10){
                break;
            }
            if (vis.get(stdto.getName()) != null){
                continue;
            }
            vis.put(stdto.getName(),String.valueOf(stdto.getValue()));
            top.add(stdto);
            i++;
        }
        response.data(top);
        return  response;
    }

    @Override
    public UniversityResponse getSalaryByAddress() {
        UniversityResponse response = new UniversityResponse();
        response.code(BaseConstant.RESPONSE_CODE_SUCCESS_200);
        response.message(BaseConstant.RESPONSE_MESSAGE_OPR_SUCCESS);
        String year = UniversityUtil.nowYear();
        List<Report> list = reportDao.selectSalaryByAddress("%"+year+"%");

        HashMap<String,List<Double>> map = new HashMap<>();
        for (Report r:list){
            if (map.get(r.getAddress())!=null){
                map.get(r.getAddress()).add(r.getSalary());
            }else{
                List<Double> doubleList = new ArrayList<>();
                doubleList.add(r.getSalary());
                map.put(r.getAddress(),doubleList);
            }
        }
        System.out.println(map);
        int size = map.size();
        SalaryByAddressDto salaryByAddressDto = new SalaryByAddressDto(new String[size],new double[size],new double[size],new double[size]);
        int flag = 0;
        for (HashMap.Entry<String, List<Double>> entry : map.entrySet()){
            entry.getKey();//地区
            double min = 0.0,max = 0.0,ave = 0.0;
            for (Double d:entry.getValue()){
                if(min == 0){
                    min = d;
                }
                if (min> d&& min!= 0){
                    min = d;
                }if(max < d){
                    max = d;
                }
                ave += d;
            }
            ave /= entry.getValue().size();
            BigDecimal bg = new BigDecimal(ave);
            double f1 = bg.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();//保留两位小数
            salaryByAddressDto.getAddress()[flag] = entry.getKey();
            salaryByAddressDto.getMinSalary()[flag] = min;
            salaryByAddressDto.getMaxSalary()[flag] = max;
            salaryByAddressDto.getAveSalary()[flag] = f1;
            flag++;
        }
        response.data(salaryByAddressDto);
        return response;
    }

    @Override
    public UniversityResponse getGraduateNumByAddress() {
        UniversityResponse response = new UniversityResponse();
        response.code(BaseConstant.RESPONSE_CODE_SUCCESS_200);
        response.message(BaseConstant.RESPONSE_MESSAGE_OPR_SUCCESS);
        List<GraNumAddressDto> list = reportDao.selectGraduateNumByAddress("%"+UniversityUtil.nowYear()+"%");
        response.data(list);
        return response;
    }

    @Override
    public UniversityResponse getSalaryByYear(EmployRateVo vo) {
        UniversityResponse response = new UniversityResponse();
        response.code(BaseConstant.RESPONSE_CODE_SUCCESS_200);
        response.message(BaseConstant.RESPONSE_MESSAGE_OPR_SUCCESS);
        List<SalaryByYearDto> list = reportDao.selectSalaryByYear(vo);
        List<SalaryByYearDto> res = new ArrayList<>();
        int flag = 4;
        String nowYear = UniversityUtil.nowYear();
        for (int i = 0; i < 5; i++) {
            SalaryByYearDto e = new SalaryByYearDto();
            e.setYear(Integer.valueOf(nowYear)-flag);
            e.setMaxSalary(0);
            e.setMinSalary(0);
            e.setSalary(0);
            e.setNum(0);
            flag--;
            res.add(e);
        }
        for (SalaryByYearDto s:list) {
            for (SalaryByYearDto r: res) {
                if (s.getYear().equals(r.getYear())){
                    r.setSalary(r.getSalary()+s.getSalary());//求和
                    if (r.getMinSalary()==0){
                        r.setMinSalary(s.getSalary());
                    }else if(r.getMinSalary()>s.getSalary()){
                        r.setMinSalary(s.getSalary());
                    }
                    if(r.getMaxSalary()<s.getSalary()){
                        r.setMaxSalary(s.getSalary());
                    }
                    r.setNum(r.getNum()+1);
                }
            }
        }
        for (SalaryByYearDto r: res) {
            if (!r.getNum().equals(0)){
                r.setSalary(UniversityUtil.saveTwoDecimal(r.getSalary()/r.getNum()));
            }
        }
        response.data(res);
        return response;

    }

    @Override
    public UniversityResponse getAveSalaryByAddress(EmployRateVo vo) {
        UniversityResponse response = new UniversityResponse();
        response.code(BaseConstant.RESPONSE_CODE_SUCCESS_200);
        response.message(BaseConstant.RESPONSE_MESSAGE_OPR_SUCCESS);
        vo.setNowYear("%"+UniversityUtil.nowYear()+"%");
        List<GraNumAddressDto> list = reportDao.selectAveSalaryByAddress(vo);
        for (GraNumAddressDto g: list) {
            g.setAveSalary(UniversityUtil.saveTwoDecimal(g.getAveSalary()/g.getValue()));
        }
        response.data(list);
        return response;
    }

    /**
     * 通过ID查询单条数据
     *
     * @param id 主键
     * @return 实例对象
     */
    @Override
    public Report queryById(Integer id) {
        return this.reportDao.queryById(id);
    }

    /**
     * 查询多条数据
     *
     * @param offset 查询起始位置
     * @param limit  查询条数
     * @return 对象列表
     */
    @Override
    public List<Report> queryAllByLimit(int offset, int limit) {
        return this.reportDao.queryAllByLimit(offset, limit);
    }

    /**
     * 新增数据
     *
     * @param report 实例对象
     * @return 实例对象
     */
    @Override
    public Report insert(Report report) {
        this.reportDao.insert(report);
        return report;
    }

    /**
     * 修改数据
     *
     * @param report 实例对象
     * @return 实例对象
     */
    @Override
    public Report update(Report report) {
        this.reportDao.update(report);
        return this.queryById(report.getId());
    }

    /**
     * 通过主键删除数据
     *
     * @param id 主键
     * @return 是否成功
     */
    @Override
    public boolean deleteById(Integer id) {
        return this.reportDao.deleteById(id) > 0;
    }
}